﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;
using System.Text;
using Models;
using ConcreteService;
using Newtonsoft.Json.Linq;
using System.Web;
using Infrastructures;
using System.IO;
using Newtonsoft.Json;
using System.Drawing;
using System.Drawing.Imaging;

namespace SponsorshipWeb.Controllers
{
    [CommonAuthorize]
    public class ProjectController : ApiController
    {
        #region Service

        ProjectService service = ServiceFactory.CreateInstance<ProjectService>();
        AssociationService assoservice = ServiceFactory.CreateInstance<AssociationService>();
        StudentService stuService = ServiceFactory.CreateInstance<StudentService>();
        UtilService utilService = ServiceFactory.CreateInstance<UtilService>();
        UserInfoService userService = ServiceFactory.CreateInstance<UserInfoService>();
        CompanyService companyService = ServiceFactory.CreateInstance<CompanyService>();
        AgentService agentService = ServiceFactory.CreateInstance<AgentService>();

        #endregion

        #region Get

        // GET api/project
        [HttpGet]
        public IHttpActionResult Get(string id)
        {
            var project = service.Get<Project>(id.DESDecrypt());
            if (project == null)
                return BadRequest();

            Dictionary<string, string> dic = project.ToDictionary();

            var data = service.GetProjectData(project.ProjectID, ProjectDataType.Project, FieldName.Introduction);

            if (data != null)
                dic.Add("Introduction", data.DataValue);

            int effNumber = service.GetContractNumber(project.ProjectID, CommonStatus.Effective);
            int confirmNumber = service.GetContractNumber(project.ProjectID, CommonStatus.Confirmed);

            dic.Add("CanEdit", confirmNumber == 0 && effNumber == 0 && project.Status == ProjectStatus.Open ? "true" : "false");
            dic.Add("CanDeleteContract", confirmNumber > 0 && effNumber == 0 && project.Status == ProjectStatus.Open ? "true" : "false");

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });

            //return Redirect("/index.html");
        }

        [AllowAnonymous]
        [HttpGet]
        public IHttpActionResult Get([FromUri]string id, [FromUri]string type)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var project = service.Get<Project>(id.DESDecrypt());
            if (project == null)
                return BadRequest();

            Dictionary<string, string> dic = project.ToDictionary();

            ListProjectData(project.ProjectID, type, dic);

            dic.Add("PastDays", DisplayUtil.GetPastDays(dic["CreateDate"]));
            dic.Add("Favorites", GetFavorites(dic["CreateDate"], project.ProjectID));

            if (dic["EndDate"].GetPastDays() > 0)
            {
                dic["Status"] = ProjectStatus.Overdue.ToString();
            }

            if (project.CreatorType == APPRole.Student)
                DisplayUtil.ListAssociation(project.CreatorID, dic, assoservice);
            else
            {
                var company = companyService.GetCompany(project.CreatorBelongID.ToString());
                if (company != null)
                {
                    dic.Add("Name", company.Name);
                    dic.Add("Nature", company.Type);
                    dic.Add("Remark", company.Sign);
                    dic.Add("TypeDetail", company.JobType);
                    dic.Add("Scale", company.Size);
                    dic.Add("LogoPath", SystemConfig.Get("UploadHttpPath") + company.LogoPath);
                }
            }

            if (user == null)
            {
                dic.Remove("SponsorBook");
                dic.Remove("ContactName");
                dic.Remove("ContactPhone");
            }

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });
        }

        [AllowAnonymous]
        [HttpGet]
        public IHttpActionResult List(string type, string number)
        {
            var lst = service.ListProjectByRole((APPRole)Enum.Parse(typeof(APPRole), type), number.ToInt());
            List<IDictionary<string, string>> lstResult = new List<IDictionary<string, string>>();
            foreach (var item in lst)
            {
                var dic = item.ToDictionary();
                dic.Add("PastDays", DisplayUtil.GetPastDays(dic["CreateDate"]));

                dic.Add("Favorites", GetFavorites(dic["CreateDate"], item.ProjectID));

                lstResult.Add(dic);
            }

            return Ok(new ListResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseList = lstResult.Select(x => (Object)x).ToList()
            });
        }

        [AllowAnonymous]
        [HttpGet]
        public IHttpActionResult ListSponsorMessage()
        {
            var lst = service.ListSponsorMessage();
            foreach (var item in lst)
            {
                try
                {
                    var date = DateTime.Parse(item["SignDate"]);
                    var dateNow = DateTime.Now;
                    var dateDiff = dateNow - date;
                    var diffDay = dateDiff.Days;
                    var diffHour = dateDiff.Hours;
                    var diffMinutes = dateDiff.Minutes;
                    var diffSeconds = dateDiff.Seconds;
                    if (diffDay > 0)
                    {
                        item["SignDate"] = diffDay + "天前";
                    }
                    else if (diffHour > 0)
                    {
                        item["SignDate"] = diffHour + "小时前";

                    }
                    else if (diffMinutes > 0)
                    {
                        item["SignDate"] = diffMinutes + "分钟前";
                    }
                    else
                    {
                        item["SignDate"] = diffSeconds + "秒前";
                    }
                }
                catch (Exception ex)
                {

                }
            }
            return Ok(new ListResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseList = lst.Select(x => (Object)x).ToList()
            });
        }

        [AllowAnonymous]
        [HttpGet]
        public IHttpActionResult ListAgentSponsorMessage()
        {
            var lst = service.ListAgentSponsorMessage();

            foreach (var item in lst)
            {
                var user = userService.Get<UserInfo>(item["AgentName"].ToString());
                if (user != null)
                    item["AgentName"] = user.NickName;
            }

            return Ok(new ListResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseList = lst.Select(x => (Object)x).ToList()
            });
        }

        [HttpGet]
        public IHttpActionResult ListContract(string id, string status)
        {
            IList<IDictionary<string, string>> modelList = new List<IDictionary<string, string>>();

            var lst = service.ListProjectContract(id.DESDecrypt().ToInt(), (CommonStatus)Enum.Parse(typeof(CommonStatus), status));
            foreach (var item in lst)
            {
                IDictionary<string, string> dic = new Dictionary<string, string>();
                var data = service.GetProjectData(item.ContractID, ProjectDataType.Contract, FieldName.Feedback);
                dic.Add("Feedback", data == null ? "" : data.DataValue);
                dic.Add("Name", item.ContractorName);
                dic.Add("CreateDate", item.CreateDate.ToString(DataFormatter.LongDate));
                dic.Add("Amount", item.Amount.ToString());
                dic.Add("Status", item.Status.ToString());
                dic.Add("ContractID", item.ContractID.DESEncrypt());
                dic.Add("SubStatus", item.SubStatus.ToString());

                var user = userService.Get<UserInfo>(item.AgentID.ToString());
                if (user != null)
                {
                    dic.Add("AgentName", user.NickName);
                    dic.Add("AgentQQ", user.QQ);
                    dic.Add("AgentPhone", user.Phone);
                }

                var contractor = userService.Get<UserInfo>(item.ContractorID.ToString());
                if (contractor != null)
                {
                    dic.Add("ContractorName", contractor.NickName);
                    dic.Add("ContractorQQ", contractor.QQ);
                    dic.Add("ContractorPhone", contractor.Phone);
                    dic.Add("CreatorType", contractor.Role == APPRole.Company ? APPRole.Student.ToString() : APPRole.Company.ToString());
                }

                modelList.Add(dic);
            }

            return Ok(new ListResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseList = modelList.Select(x => (Object)x).ToList()
            });
        }

        [HttpGet]
        public IHttpActionResult GetContract(string id)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            Dictionary<string, string> dic = new Dictionary<string, string>();

            var contract = service.GetProjectContract(id.DESDecrypt().ToInt());
            if (contract == null)
                return BadRequest();

            var project = service.Get<Project>(contract.ProjectID.ToString());
            if (project == null)
                return BadRequest();

            dic.Add("ProjectName", project.ProjectName);
            dic.Add("CreateDate", project.CreateDate.ToString(DataFormatter.ShortDate));

            var contractor = userService.Get<UserInfo>(contract.ContractorID.ToString());
            if (contractor == null)
                return BadRequest();

            dic.Add("Name", contract.ContractorName);
            dic.Add("ContractID", contract.ContractID.DESEncrypt());
            dic.Add("ContractDate", contract.CreateDate.ToString(DataFormatter.LongDate));
            dic.Add("ContractorName", contractor.NickName);
            dic.Add("ContractorQQ", contractor.QQ);
            dic.Add("ContractorPhone", contractor.Phone);
            dic.Add("SignDate", contract.SignDate.ToString(DataFormatter.LongDate));
            dic.Add("Status", contract.Status.ToString());
            dic.Add("SubStatus", contract.SubStatus.ToString());
            dic.Add("TemplateVersion", contract.TemplateVersion);
            dic.Add("UserType", user.UserType.ToString());
            dic.Add("ContractCode", contract.ContractCode);
            dic.Add("CreateBySelf", project.CreatorID == user.UserID ? "Y" : "N");

            //if (user.UserType == APPRole.Agent)
            //{
            var student = userService.Get<UserInfo>(project.CreatorID.ToString());
            if (student != null)
            {
                dic.Add("Creator", student.NickName);
                dic.Add("CreatorQQ", student.QQ);
                dic.Add("CreatorPhone", student.Phone);
                dic.Add("CreatorName", project.CreatorName);
            }
            //}

            var data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractStep1Date);
            dic.Add("ContractStep1Date", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractStep2Date);
            dic.Add("ContractStep2Date", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractStep3Date);
            dic.Add("ContractStep3Date", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractStep4Date);
            dic.Add("ContractStep4Date", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractStep5Date);
            dic.Add("ContractStep5Date", data == null ? "" : data.DataValue);

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });
        }

        [HttpGet]
        public IHttpActionResult GetContractDetails(string id)
        {
            var contract = service.GetProjectContract(id.DESDecrypt().ToInt());
            if (contract == null)
                return BadRequest();

            var data = service.GetProjectData(contract.ProjectID, contract.ContractID, FieldName.ContractContent);
            if (data == null)
                return BadRequest();

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = JsonConvert.DeserializeObject<Dictionary<string, string>>(data.DataValue)
            });
        }

        [HttpGet]
        public IHttpActionResult GetSponsorContract(string id)
        {
            var loginInfo = AuthUtil.GetAuthentication();

            Dictionary<string, string> dic = new Dictionary<string, string>();

            var contract = service.GetProjectContract(id.DESDecrypt().ToInt());
            if (contract == null)
                return BadRequest();

            var project = service.Get<Project>(contract.ProjectID.ToString());
            if (project == null)
                return BadRequest();

            var contractor = userService.Get<UserInfo>(contract.ContractorID.ToString());
            if (contractor == null)
                return BadRequest();

            var data = service.GetProjectData(project.ProjectID, ProjectDataType.Project, FieldName.Introduction);

            if (data != null)
                dic.Add("Introduction", data.DataValue);

            data = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.Feedback);
            if (data != null)
                dic.Add("Feedback", data.DataValue);

            dic.Add("ProjectID", project.ProjectID.DESEncrypt());
            dic.Add("ProjectName", project.ProjectName);
            dic.Add("CreatorType", project.CreatorType.ToString());
            dic.Add("Amount", contract.Amount.ToString());
            dic.Add("CreateDate", project.CreateDate.ToString(DataFormatter.ShortDate));
            dic.Add("Name", project.CreatorName);
            dic.Add("ContractID", contract.ContractID.DESEncrypt());
            dic.Add("ContractDate", contract.CreateDate.ToString(DataFormatter.LongDate));
            dic.Add("ContractorName", contractor.NickName);
            dic.Add("ContractorQQ", contractor.QQ);
            dic.Add("ContractorPhone", contractor.Phone);
            dic.Add("Status", contract.Status.ToString());
            dic.Add("SubStatus", contract.SubStatus.ToString());
            dic.Add("PercentageMoney", "NULL");
            dic.Add("UserType", loginInfo.UserType.ToString());

            var student = userService.Get<UserInfo>(project.CreatorID.ToString());
            if (student != null)
            {
                dic.Add("Creator", student.NickName);
                dic.Add("CreatorQQ", student.QQ);
                dic.Add("CreatorPhone", student.Phone);
            }

            if (loginInfo.UserType == APPRole.Agent)
            {
                dic.Add("CreatorName", contract.ContractorName);
                var contractData = service.GetProjectData(contract.ContractID, ProjectDataType.Contract, FieldName.ContractContent);
                if (contractData != null)
                {
                    var dicData = JsonConvert.DeserializeObject<Dictionary<string, string>>(contractData.DataValue);
                    dic["PercentageMoney"] = dicData["PercentageMoney"];
                }
            }

            if (loginInfo.UserType == APPRole.Company || loginInfo.UserType == APPRole.Student)
            {
                var user = userService.Get<UserInfo>(contract.AgentID.ToString());
                if (user != null)
                {
                    dic.Add("AgentName", user.NickName);
                    dic.Add("AgentQQ", user.QQ);
                    dic.Add("AgentPhone", user.Phone);
                }
            }

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });
        }

        [HttpGet]
        public IHttpActionResult CheckFavorites(string id)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var obj = service.GetProjectCollection(user.UserID, id.DESDecrypt().ToInt());

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = obj == null ? "False" : "True"
            });
        }

        [HttpGet]
        public IHttpActionResult RemoveFavorites(string id)
        {
            var user = AuthUtil.GetAuthentication();
            var collect = service.GetProjectCollection(user.UserID, id.DESDecrypt().ToInt());
            if (collect == null)
                return BadRequest("未找到此收藏");

            service.DeleteProjectCollection(collect.CollectionID, user.UserID.ToString());

            return Ok();
        }

        [HttpGet]
        public IHttpActionResult GetContractFeedback(string id)
        {
            Dictionary<string, string> dic = new Dictionary<string, string>();

            int contractID = id.DESDecrypt().ToInt();

            var data = service.GetProjectData(contractID, ProjectDataType.Contract, FieldName.PhotosUrl);
            dic.Add("PhotosUrl", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contractID, ProjectDataType.Contract, FieldName.TweetsUrl);
            dic.Add("TweetsUrl", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contractID, ProjectDataType.Contract, FieldName.VideoUrl);
            dic.Add("VideoUrl", data == null ? "" : data.DataValue);

            data = service.GetProjectData(contractID, ProjectDataType.Contract, FieldName.ActivitySummary);
            dic.Add("ActivitySummary", data == null ? "" : data.DataValue);

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });
        }

        [HttpGet]
        public IHttpActionResult GetContractData(string id, string name)
        {
            Dictionary<string, string> dic = new Dictionary<string, string>();
            var data = service.GetProjectData(id.DESDecrypt().ToInt(), ProjectDataType.Contract, (FieldName)Enum.Parse(typeof(FieldName), name));

            dic.Add("Name", data.DataValue);

            return Ok(new DictResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseDict = dic
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpGet]
        public IHttpActionResult ActiveProject(string id)
        {
            var user = AuthUtil.GetAuthentication();

            Project pro = service.Get<Project>(id.DESDecrypt());

            if (pro == null || pro.CreatorID != user.UserID)
                return BadRequest("无修改活动权限");

            pro.Status = ProjectStatus.Open;
            service.Update<Project>(pro, user.UserID.ToString());

            return Ok();
        }

        #endregion

        #region Post

        [HttpPost]
        [UserRole(APPRole.Student, APPRole.Company)]
        public IHttpActionResult DeleteOrEditProject([FromBody]JObject value)
        {
            var user = AuthUtil.GetAuthentication();

            string projectID = GetValue(value, "id").DESDecrypt();

            Project pro = service.Get<Project>(projectID);

            if (pro == null || pro.CreatorID != user.UserID)
                return BadRequest("无修改活动权限");

            var lst = service.ListProjectContract(projectID.ToInt(), CommonStatus.All);
            int count = lst.Count(x => x.Status == CommonStatus.Confirmed || x.Status == CommonStatus.Effective || x.Status == CommonStatus.Closed);
            if (count > 0)
                return BadRequest("当前有未确认的邀请或已生成的合同，无法执行此操作");

            switch (GetValue(value, "type"))
            {
                case "Edit":
                    //return Ok("");
                    break;
                case "Delete":
                    pro.Status = ProjectStatus.Cancel;
                    service.Update(pro, user.UserID.ToString());
                    break;
            }

            return Ok();
        }

        [HttpPost]
        public IHttpActionResult ListProjectsByStatus([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            IDictionary<SearchKey, string> dic = new Dictionary<SearchKey, string>();
            dic.Add(SearchKey.ProjectStatus, GetValue(value, SearchKey.ProjectStatus));
            dic.Add(SearchKey.CreatorID, user.UserID.ToString());
            dic.Add(SearchKey.SearchFrom, user.UserType.ToString());
            var lst = service.Search(dic, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));
            ModelList<IDictionary<string, string>> modelList = new ModelList<IDictionary<string, string>>();

            foreach (var item in lst)
            {
                var lstContract = service.ListProjectContract(item.ProjectID, CommonStatus.All);

                IDictionary<string, string> dicProject = new Dictionary<string, string>();
                dicProject.Add("ProjectID", item.ProjectID.DESEncrypt());
                dicProject.Add("ProjectName", item.ProjectName);
                dicProject.Add("CreateDate", item.CreateDate.ToString(DataFormatter.ShortDate));
                dicProject.Add("ContractCount", lstContract.Count == 0 ? "0" : lstContract.Count.ToString());
                dicProject.Add("UnAcceptCount", lstContract.Count == 0 ? "0" : lstContract.Count(x => x.Status == CommonStatus.Confirmed).ToString());
                dicProject.Add("Amount", lstContract.Count == 0 ? "0" : lstContract.Where(x => x.Status == CommonStatus.Effective).Sum(x => x.Amount).ToString());

                modelList.Add(dicProject);
            }

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = modelList.ToListObject()
            });
        }

        [HttpPost]
        public IHttpActionResult ListMyMessages([FromBody]JObject value)
        {
            var user = AuthUtil.GetAuthentication();

            var json = utilService.ListUserMessage(user.UserID.ToString(), GetIntValue(value, "Start"), GetIntValue(value, "Limit"));

            return Ok(new JsonResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseJson = json
            });
        }

        [AllowAnonymous]
        [HttpPost]
        public IHttpActionResult ListProjectsByBelongID([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var lst = service.ListProjectByBelongID(GetIntValue(value, "BelongID"), GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));
            ModelList<IDictionary<string, string>> modelList = new ModelList<IDictionary<string, string>>();

            foreach (var item in lst)
                modelList.Add(item.ToDictionary());

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = modelList.ToListObject()
            });
        }

        [HttpPost]
        public IHttpActionResult ListContractByStatus([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();
            CommonStatus status = (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "Status"));

            IList<CommonStatus> lstStatus = null;
            ModelList<IDictionary<string, string>> lst = null;

            if (user.UserType == APPRole.Student || user.UserType == APPRole.Company)
            {
                if (status == CommonStatus.Closed)
                {
                    lstStatus = new List<CommonStatus>();
                    lstStatus.Add(CommonStatus.Closed);
                    lstStatus.Add(CommonStatus.Cancelled);
                    lst = service.ListContractByStatus(user.UserID, lstStatus, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));
                }
                else
                    lst = service.ListContractByStatus(user.UserID, status, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));

                foreach (var item in lst)
                {
                    if (item["CreatorID"] != user.UserID.ToString())
                    {
                        item["ContractorName"] = item["CreatorName"];
                    }
                }
            }
            else
            {
                if (status == CommonStatus.Closed)
                {
                    lstStatus = new List<CommonStatus>();
                    lstStatus.Add(CommonStatus.Closed);
                    lstStatus.Add(CommonStatus.Cancelled);
                }
                else
                {
                    lstStatus = new List<CommonStatus>();
                    lstStatus.Add(CommonStatus.Effective);
                }

                lst = service.ListContractByAgent(user.UserID, lstStatus, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));
                foreach (var item in lst)
                {
                    var data = service.GetProjectData(item["ContractID"].DESDecrypt().ToInt(), ProjectDataType.Contract, FieldName.ContractContent);
                    if (data != null)
                    {
                        var dic = JsonConvert.DeserializeObject<Dictionary<string, string>>(data.DataValue);
                        item["Amount"] = dic["PercentageMoney"];
                    }
                    else
                    {
                        item["Amount"] = "";
                    }
                }
            }

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = lst.ToListObject()
            });
        }

        [HttpPost]
        public IHttpActionResult ListSponsorContract([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            CommonStatus status = (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "Status"));

            IList<CommonStatus> lstStatus = null;

            if (status == CommonStatus.Closed)
                lstStatus = new List<CommonStatus>() { CommonStatus.Overdue, CommonStatus.Rejected, CommonStatus.Cancelled, CommonStatus.Closed };
            else
                lstStatus = new List<CommonStatus>() { CommonStatus.Confirmed, CommonStatus.Effective };

            ModelList<IDictionary<string, string>> lst = null;

            if (user.UserType == APPRole.Student || user.UserType == APPRole.Company)
            {
                lst = service.ListSponsorContract(user.UserID, lstStatus, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));

                foreach (var item in lst)
                    item.Add("ContractNumber", service.GetContractNumber(item["ProjectID"].DESDecrypt().ToInt()).ToString());
            }
            else
            {
                lst = service.ListContractByAgent(user.UserID, lstStatus, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));

                foreach (var item in lst)
                {
                    item.Add("ContractNumber", item["CreatorName"]);
                    var data = service.GetProjectData(item["ContractID"].DESDecrypt().ToInt(), ProjectDataType.Contract, FieldName.ContractContent);
                    if (data != null)
                    {
                        var dic = JsonConvert.DeserializeObject<Dictionary<string, string>>(data.DataValue);
                        item["SponsorAmount"] = dic["PercentageMoney"];
                    }
                    else
                    {
                        item["SponsorAmount"] = "";
                    }
                }
            }

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = lst.ToListObject()
            });
        }

        [HttpPost]
        public IHttpActionResult ListProjectCollection([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var lst = service.ListProjectCollection(user.UserID, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));

            foreach (var item in lst)
                item.Add("ContractNumber", service.GetContractNumber(item["ProjectID"].DESDecrypt().ToInt()).ToString());

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = lst.ToListObject()
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult CreateProject([FromBody]JObject value)
        {
            //var user = AuthUtil.GetAuthentication();
            //if (user == null)
            //    return BadRequest();

            LoginInfo user = AuthUtil.GetAuthentication();

            if (user.UserType != APPRole.Student && user.UserType != APPRole.Company)
                return BadRequest("无创建活动权限");

            var userInfo = userService.Get<UserInfo>(user.UserID.ToString());
            if (userInfo.Status == CommonStatus.FiveStep)
                return BadRequest("用户信息审核中，请审核通过后提交");

            if (userInfo.Status != CommonStatus.Verified)
                return BadRequest("请完成用户信息后提交活动");

            var count = service.CountProjectCreatedPerDay(user.UserID);
            if (count >= SystemConfig.Get("MaxProjectCreatePerDay").ToInt())
                return BadRequest("已达到一天可创建的活动数上限");

            Project project = new Project();

            if (user.UserType == APPRole.Student)
            {
                Student stu = stuService.Get<Student>(user.UserID.ToString());
                School school = AppConfig.GetSchool(stu.SchoolNO);
                //如何分开区域和地址？搜索的时候需要区域，但是创建的时候只有一个地址
                value["Area"] = school.CityNO;
                value["AreaDetails"] = school.DetailSchoolName;
                var asso = utilService.ListRelationship(RelationshipFun.AssociationToStudent, user.UserID).FirstOrDefault();
                //广州大学-cos社
                project.CreatorName = asso.NameFrom;
                project.Address = value["Address"].ToString();
                project.CreatorBelongID = asso.ID;
            }
            else
            {
                //project.CreatorName = "百事可乐";
                value["AreaDetails"] = AppConfig.GetAreaName(value["Area"].ToString().ToInt());
                //company的id
                var company = companyService.GetCompany(user.UserID.ToString());
                project.CreatorBelongID = company.CompanyNO;
                project.CreatorName = company.Name;
            }

            project.ProjectName = value["ProjectName"].ToString();
            project.Amount = value["Amount"].ToString().ToDouble();
            project.StartDate = value["StartDate"].ToString().ToDateTime();
            project.EndDate = value["EndDate"].ToString().ToDateTime();
            project.Status = ProjectStatus.Draft;
            project.CreatorID = user.UserID;
            project.CreateDate = DateTime.Now;
            project.CreatorType = user.UserType;

            service.Create(project, user.UserID.ToString());

            CreateData(project.ProjectID, user, value);

            CreateProjectSearch(project.ProjectID, value, user);

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = project.ProjectID.DESEncrypt()
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult UpdateProject([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var project = service.Get<Project>(GetValue(value, "ID").DESDecrypt());
            if (project.CreatorID != user.UserID)
                return BadRequest("无修改此活动的权限");

            project.ProjectName = value["ProjectName"].ToString();
            project.Amount = value["Amount"].ToString().ToDouble();
            project.StartDate = value["StartDate"].ToString().ToDateTime();
            project.EndDate = value["EndDate"].ToString().ToDateTime();

            if (user.UserType == APPRole.Student)
            {
                Student stu = stuService.Get<Student>(user.UserID.ToString());
                School school = AppConfig.GetSchool(stu.SchoolNO);
                value["Area"] = school.CityNO;
                project.Address = value["Address"].ToString();
            }

            service.Update(project, user.UserID.ToString());

            service.DeleteProjectData(project.ProjectID, ProjectDataType.Project, user.UserID.ToString());
            CreateData(project.ProjectID, user, value);

            service.DeleteProjectSearch(project.ProjectID.ToString());
            CreateProjectSearch(project.ProjectID, value, user);

            return Ok();
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult CreateContract([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            if (user.UserType != APPRole.Student && user.UserType != APPRole.Company)
                return BadRequest("无创建合同权限");

            string projectID = GetValue(value, "ProjectID").DESDecrypt();

            var project = service.Get<Project>(projectID);
            if (project == null)
                return BadRequest("此活动不存在");

            if (project.CreatorType == user.UserType)
                return BadRequest("无创建合同权限");

            var contract = service.GetProjectContract(projectID.ToInt(), user.UserID);
            if (contract != null)
                return BadRequest("已邀请此活动");

            ProjectContract obj = new ProjectContract();

            if (!string.IsNullOrWhiteSpace(value["AgentID"].ToString()))
            {
                int agentID = agentService.GetAgentID(value["AgentID"].ToString());
                if (agentID == 0)
                    return BadRequest("未找到此代理管，请重新输入");

                obj.AgentID = agentID;
            }

            obj.ProjectID = project.ProjectID;
            obj.CreateDate = DateTime.Now;
            obj.Amount = value["Amount"].ToString().ToDouble();
            obj.Status = CommonStatus.Confirmed;

            if (user.UserType == APPRole.Student)
            {
                //var student = stuService.Get<Student>(user.UserID.ToString());
                var asso = utilService.ListRelationship(RelationshipFun.AssociationToStudent, user.UserID).FirstOrDefault();
                obj.ContractorID = user.UserID;
                obj.ContractorName = asso.NameFrom;
            }
            else
            {
                var company = companyService.GetCompany(user.UserID.ToString());
                obj.ContractorID = company.CompanyNO;
                obj.ContractorName = company.Name;
            }

            service.CreateProjectContract(obj, user.UserID.ToString());

            CreateData(obj.ProjectID, obj.ContractID, user, FieldName.Feedback, value);

            MessageUtil.SendMessage(obj.Status, user.UserID, 0, obj);

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = obj.ContractorID.ToString()
            });

        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult UpdateContractAmount([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            if (user == null)
                return BadRequest();

            var contract = service.GetProjectContract(GetValue(value, "ID").DESDecrypt().ToInt());

            if (contract == null)
                return BadRequest();

            if (contract.Status != CommonStatus.Confirmed)
                return BadRequest("只允许在未确认状态下修改金额");

            if (user.UserID != contract.ContractorID)
            {
                var project = service.Get<Project>(contract.ProjectID.ToString());
                if (project.CreatorID != user.UserID)
                    return BadRequest("无修改活动金额权限");
            }

            contract.Amount = value["Amount"].ToString().ToDouble();
            contract.SubStatus = CommonStatus.SponMoneyChanged;

            service.UpdateProjectContract(contract, user.UserID.ToString());

            return Ok();
        }

        [AllowAnonymous]
        [HttpPost]
        public IHttpActionResult Search([FromBody]JObject value)
        {
            //var user = AuthUtil.GetAuthentication();
            //if (user == null)
            //    return BadRequest();

            ModelList<IDictionary<string, string>> modelList = new ModelList<IDictionary<string, string>>();

            IDictionary<SearchKey, string> dic = ListSearchCondition(value);
            var lst = service.Search(dic, GetIntValue(value, SearchKey.Start), GetIntValue(value, SearchKey.Limit));

            foreach (var item in lst)
            {
                var dicResult = item.ToDictionary();
                dicResult.Add("PastDays", DisplayUtil.GetPastDays(dicResult["CreateDate"]));
                dicResult.Add("Favorites", GetFavorites(dicResult["CreateDate"], item.ProjectID));
                modelList.Add(dicResult);
            }

            return Ok(new ModelListResponse()
            {
                Status = ResponseStatus.OK(),
                Count = lst.TotalCount,
                ResponseList = modelList.ToListObject()
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult UpdateContractStatus([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            int contractID = GetValue(value, "ContractID").DESDecrypt().ToInt();

            var contract = service.GetProjectContract(contractID);
            if (contract == null)
                return BadRequest("未找到此合同");

            if (user.UserID != contract.ContractorID)
            {
                var project = service.Get<Project>(contract.ProjectID.ToString());
                if (project == null)
                    return BadRequest("未找到此活动");

                if (project.CreatorID != user.UserID)
                    return BadRequest("无修改活动权限");
            }

            service.UpdateContractStatus(contractID, (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "Status")),
                user.UserID, GetValue(value, "Remark"));

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = contractID.ToString()
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult UpdateContractSubStatus([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            int contractID = GetValue(value, "ContractID").DESDecrypt().ToInt();

            var contract = service.GetProjectContract(contractID);
            if (contract == null)
                return BadRequest("未找到此合同");

            if (user.UserID != contract.ContractorID)
            {
                var project = service.Get<Project>(contract.ProjectID.ToString());
                if (project.CreatorID != user.UserID)
                    return BadRequest("无修改活动权限");
            }

            service.UpdateContractSubStatus(contractID, (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "Status")),
                user.UserID, GetValue(value, "Remark"));

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = contractID.ToString()
            });
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult CancelContractStatusByProject([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            string projectID = GetValue(value, "ProjectID").DESDecrypt();

            var project = service.Get<Project>(projectID);
            if (project.CreatorID != user.UserID)
                return BadRequest("无修改活动权限");

            service.UpdateContractStatusByProject(projectID.ToInt(), CommonStatus.Cancelled, user.UserID);

            return Ok();
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult CancelContract([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            int contractID = GetValue(value, "ContractID").DESDecrypt().ToInt();

            var contract = service.GetProjectContract(contractID);
            if (contract == null)
                return BadRequest("未找到此合同");

            if (user.UserID != contract.ContractorID)
            {
                var project = service.Get<Project>(contract.ProjectID.ToString());
                if (project.CreatorID != user.UserID)
                    return BadRequest("无修改活动权限");
            }

            CommonStatus status = CommonStatus.All;
            string subStatus = GetValue(value, "SubStatus");
            if (!subStatus.IsNullOrEmpty())
                status = (CommonStatus)Enum.Parse(typeof(CommonStatus), subStatus);

            service.UpdateContractStatus(contractID, (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "Status")),
               status, user.UserID, GetValue(value, "CancelRemark"));

            return Ok(new StringResponse()
            {
                Status = ResponseStatus.OK(),
                ResponseStr = contractID.ToString()
            });
        }

        [HttpPost]
        public IHttpActionResult AddToFavorites([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            var project = service.Get<Project>(GetValue(value, "ProjectID").DESDecrypt());
            if (project == null)
                return BadRequest();

            ProjectCollection obj = new ProjectCollection(user.UserID, project.ProjectID, project.CreatorType);

            service.CreateProjectCollection(obj, user.UserID.ToString());

            return Ok();
        }

        [UserRole(APPRole.Student, APPRole.Company)]
        [HttpPost]
        public IHttpActionResult SubmitFeedback([FromBody]JObject value)
        {
            LoginInfo user = AuthUtil.GetAuthentication();

            int id = GetValue(value, "ContractID").DESDecrypt().ToInt();
            var contract = service.GetProjectContract(id);
            if (contract == null)
                return BadRequest("未找到此合同");

            string type = GetValue(value, "Type");

            if (user.UserID != contract.ContractorID)
            {
                var project = service.Get<Project>(contract.ProjectID.ToString());
                if (project.CreatorID != user.UserID)
                    return BadRequest("无修改活动权限");
            }

            if (type == "Submit")
            {
                CreateData(contract.ProjectID, contract.ContractID, user, FieldName.PhotosUrl, value);
                CreateData(contract.ProjectID, contract.ContractID, user, FieldName.TweetsUrl, value);
                CreateData(contract.ProjectID, contract.ContractID, user, FieldName.VideoUrl, value);
                CreateData(contract.ProjectID, contract.ContractID, user, FieldName.ActivitySummary, value);
            }
            else
            {
                UpdateData(contract.ContractID, FieldName.PhotosUrl, value, user.UserID);
                UpdateData(contract.ContractID, FieldName.TweetsUrl, value, user.UserID);
                UpdateData(contract.ContractID, FieldName.VideoUrl, value, user.UserID);
                UpdateData(contract.ContractID, FieldName.ActivitySummary, value, user.UserID);
            }

            service.UpdateContractSubStatus(contract.ContractID, CommonStatus.FeedbackSubmitted, user.UserID);

            return Ok();
        }

        [HttpPost]
        public IHttpActionResult UploadFile(FileType type, string projectID)
        {
            var user = AuthUtil.GetAuthentication();

            var httpPostedFile = HttpContext.Current.Request.Files;

            IList<FileSystem> lst = new List<FileSystem>();

            int id = projectID.DESDecrypt().ToInt();

            for (int i = 0; i < httpPostedFile.Count; i++)
            {
                HttpPostedFile file = httpPostedFile[i];

                lst.Clear();

                if (type == FileType.ActImg)
                {
                    if (file.FileName.ToLower() == "cover.jpg" || file.FileName.ToLower() == "cover.jpeg")
                    {
                        using (Image image = Image.FromStream(file.InputStream).GetThumbnailImage(215, 139, () => { return false; }, IntPtr.Zero))
                            FileUtil.SaveFile(file, FileType.ActCoverThumb, lst, id, user.UserID.ToString(), image, false);
                    }

                    //lst = utilService.ListFileSystem(FileType.ActImg, projectID);

                    using (Image image = Image.FromStream(file.InputStream).GetThumbnailImage(383, 229, () => { return false; }, IntPtr.Zero))
                        FileUtil.SaveFile(file, FileType.ActImgThumb, lst, id, user.UserID.ToString(), image);
                }
                else
                    FileUtil.SaveFile(file, type, lst, id, user.UserID.ToString());
            }

            return Ok();
        }

        [HttpPost]
        public IHttpActionResult UpdateMessage([FromBody]JObject value)
        {
            var user = AuthUtil.GetAuthentication();

            var msg = utilService.GetUserMessage(GetIntValue(value, "id"));
            if (msg == null)
                return BadRequest("未找到此消息");

            msg.Status = (CommonStatus)Enum.Parse(typeof(CommonStatus), GetValue(value, "type"));

            utilService.UpdateUserMessage(msg, user.UserID.ToString());

            return Ok();
        }

        #endregion

        #region Helper

        private void UpdateData(int id, FieldName name, JObject value, int oper, ProjectDataType type = ProjectDataType.Contract)
        {
            var data = service.GetProjectData(id, type, name);
            if (data == null)
                return;

            data.DataValue = GetValue(value, name);
            service.UpdateProjectData(data, oper.ToString());
        }

        private void CreateProjectSearch(int projectNo, JObject value, LoginInfo user)
        {
            StringBuilder sb = new StringBuilder(200);

            switch (user.UserType)
            {
                case APPRole.Student:

                    var student = stuService.Get<Student>(user.UserID.ToString());
                    var word = utilService.GetSpliteWord(student.SchoolNO);
                    if (word != null)
                        sb.Append(word.Value + " " + word.SpliteValue + " ");
                    break;
                case APPRole.Company:
                    var compnayWord = utilService.GetSpliteWord(user.UserID);
                    if (compnayWord != null)
                        sb.Append(compnayWord.Value + " " + compnayWord.SpliteValue + " ");
                    break;
            }

            var dic = ListSearchCondition(value, "create");
            foreach (var item in dic)
            {
                if (!item.Value.IsNullOrEmpty())
                    sb.Append(item.Value + " ");
            }

            ProjectSearch obj = new ProjectSearch(projectNo, sb.ToString());
            service.CreateProjectSearch(obj, user.UserID.ToString());
        }

        private IDictionary<SearchKey, string> ListSearchCondition(JObject value, string type = "search")
        {
            IDictionary<SearchKey, string> dic = new Dictionary<SearchKey, string>();

            if (type == "search")
            {
                dic.Add(SearchKey.SchoolName, GetValue(value, SearchKey.SchoolName));
                dic.Add(SearchKey.CompanyName, GetValue(value, SearchKey.CompanyName));
                dic.Add(SearchKey.StartDate, GetValue(value, SearchKey.StartDate));
                dic.Add(SearchKey.EndDate, GetValue(value, SearchKey.EndDate));
                dic.Add(SearchKey.SearchFrom, GetValue(value, SearchKey.SearchFrom));
            }

            dic.Add(SearchKey.Area, GetValue(value, SearchKey.Area));
            dic.Add(SearchKey.ActivityType, GetValue(value, SearchKey.ActivityType));
            dic.Add(SearchKey.StudentInterval, GetValue(value, SearchKey.StudentInterval));

            if (type == "create")
            {
                var money = GetIntValue(value, "Amount");
                dic.Add(SearchKey.SponsorMoney, AppConfig.GetBaseData(BaseDataFun.SponsorMoney, money).RuleNO.ToString());
            }
            else
                dic.Add(SearchKey.SponsorMoney, GetValue(value, SearchKey.SponsorMoney));

            return dic;
        }

        private void CreateData(int projectID, LoginInfo user, JObject value)
        {
            var lst = AppConfig.ListFieldByRole(user.UserType);

            foreach (var item in lst)
            {
                ProjectData data = new ProjectData();
                data.DataType = ProjectDataType.Project;
                data.DataName = item;
                data.DataValue = GetValue(value, item);
                data.ProjectID = projectID;
                data.UpdateDate = DateTime.Now;
                data.UpdateUser = user.UserID;

                service.CreateProjectData(data, user.UserID.ToString());
            }
        }

        private void CreateData(int projectID, int contractID, LoginInfo user, FieldName name, JObject value)
        {
            ProjectData data = new ProjectData();
            data.DataType = ProjectDataType.Contract;
            data.DataName = name;
            data.DataValue = GetValue(value, name);
            data.ProjectID = projectID;
            data.ContractID = contractID;
            data.UpdateDate = DateTime.Now;
            data.UpdateUser = user.UserID;

            service.CreateProjectData(data, user.UserID.ToString());
        }

        private void ListProjectData(int id, string type, Dictionary<string, string> dic)
        {
            var lst = service.ListProjectData(id, (ProjectDataType)Enum.Parse(typeof(ProjectDataType), type));
            foreach (var item in lst)
            {
                string value = item.DataValue;

                if (value.IsNullOrEmpty() && item.DataName != FieldName.AreaDetails)
                    continue;

                switch (item.DataName)
                {
                    case FieldName.ActivityType:
                    case FieldName.StudentInterval:
                        var baseData = AppConfig.GetBaseData(value.ToInt());
                        value = baseData.Description;
                        break;
                    //case FieldName.Area:
                    //    value = item.DataValue;
                    //    break;
                }

                dic.Add(item.DataName.ToString(), value);
            }
            var lstfileSystem = utilService.ListFileSystem(FileType.All, id);
            int i = 1;
            foreach (var item in lstfileSystem)
            {
                if (item.Fun == FileType.SponsorBook)
                    dic.Add("SponsorBook", item.Path);
                else if (item.Fun == FileType.ActImgThumb)
                {
                    dic.Add("ActImg" + i, item.Path);
                    i++;
                }
            }
        }

        private string GetValue(JObject value, Enum name)
        {
            if (value == null)
                return string.Empty;

            return value[name.ToString()] == null ? string.Empty : value[name.ToString()].ToString();
        }

        private string GetValue(JObject value, string name)
        {
            if (value == null)
                return string.Empty;

            return value[name] == null ? string.Empty : value[name].ToString();
        }

        private int GetIntValue(JObject value, Enum name)
        {
            if (value == null)
                return 0;

            return value[name.ToString()] == null ? 0 : value[name.ToString()].ToString().ToInt();
        }

        private int GetIntValue(JObject value, string name)
        {
            if (value == null)
                return 0;

            return value[name] == null ? 0 : value[name].ToString().ToInt();
        }

        private string GetFavorites(string date, int projectID)
        {
            return (date.GetPastDays() * SystemConfig.Get("FavoritesTimes").ToInt() + service.CountProjectCollection(projectID)).ToString();
        }

        #endregion
    }
}
